﻿using Sys.Workflow.Bpmn.Models;
using Sys.Workflow.Engine.Impl.Interceptor;
using Sys.Workflow.Engine.Impl.Persistence.Entity;
using Sys.Workflow.Engine.Impl.Util;
using Sys.Workflow.Engine.Tasks;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Sys.Workflow.Engine.impl.cmd
{
    public class TaskJumpCmd : ICommand<object>
    {
        // 任务ID
        public string taskId;

        // 目标节点ID
        public string targetNodeId;

        public string? assignee;

        public string? processInstanceId;

        public TaskJumpCmd(string taskId, string targetNodeId, string? assignee, string processInstanceId)
        {
            this.taskId = taskId;
            this.targetNodeId = targetNodeId;
            this.assignee = assignee;
            this.processInstanceId = processInstanceId;
        }

        public object Execute(ICommandContext commandContext)
        {
            // 获取命令执行实体管理器
            IExecutionEntityManager executionEntityManager = commandContext.ExecutionEntityManager;
            // 获取任务对象管理器
            ITaskEntityManager taskEntityManager = commandContext.TaskEntityManager;
            // 根据任务ID获取任务对象
            ITaskEntity taskEntity = taskEntityManager.FindById<ITaskEntity>(taskId);
            // 根据任务对象属性excutionId获取流程实例对象
            IExecutionEntity executionEntity = executionEntityManager.FindById<IExecutionEntity>(taskEntity.ExecutionId);
            // 根据流程执行实例中的流程模板定义ID属性获取流程对象
            Process process = ProcessDefinitionUtil.GetProcess(executionEntity.ProcessDefinitionId);
            // 根据目标节点ID获取对应节点
            FlowElement targetFlowElement = process.GetFlowElement(targetNodeId, true);
            if (assignee is not null && targetFlowElement is UserTask)
            {
                ((UserTask)targetFlowElement).Assignee = assignee;
            }
            // 在上一流程实例对象中改变当前节点
            executionEntity.CurrentFlowElement = targetFlowElement;
            // 获取流程计划 注: 翻译可能不对
            IActivitiEngineAgenda agenda = commandContext.Agenda;
            // 更新流程实例对象 注: 翻译可能不对
            agenda.PlanContinueProcessInCompensation(executionEntity);
            // 根据在任务对象中删除之前任务
            taskEntityManager.Delete(taskEntity);

            return null;
        }
    }
}
